<template>
  <div class="correct-detail-container">
    <Breadcrumb>
      <template #bread-name> 作业批改 </template>
      <template #bread-right>
        <div class="jump-btn" @click="toSingleCorrect">按题批改</div></template
      >
    </Breadcrumb>
    <main class="content flex">
      <div class="content-left">
        <div class="flex-between">
          <div class="left-title text-ellipsis" :title="taskInfo.name">
            {{ taskInfo.name }}
          </div>
          <el-select
            v-model="selectClass"
            placeholder="请选择班级"
            value-key="classId"
            style="width: 120px"
          >
            <el-option
              v-for="item in taskInfo.classList"
              :key="item.classId"
              :label="item.className"
              :value="item"
            />
          </el-select>
        </div>
        <template v-if="curStudentIndex !== null">
          <div class="title flex-between">
            <span>{{ studentList[curStudentIndex]?.student_name }}</span>
            <span
              >待批改：{{
                studentList[curStudentIndex]?.un_grade_count
              }}题</span
            >
          </div>
          <div class="student-list flex-column">
            <div
              class="student-item hover flex-between"
              :class="[curStudentIndex === index && 'student-item-active']"
              @click="onChangeStu(index)"
              v-for="(student, index) in studentList"
              :key="index"
            >
              <span>{{ student.student_name }}</span>
              <span class="count">{{ student.un_grade_count }}题</span>
            </div>
          </div>
          <div class="btn-list flex-around">
            <div
              class="btn-item hover flex-center"
              :class="[curStudentIndex === 0 && 'disabled']"
              @click="onChangeStu('pre')"
            >
              上一个学生
            </div>
            <div
              class="btn-item hover flex-center"
              :class="[
                !studentList.length ||
                curStudentIndex === studentList.length - 1
                  ? 'disabled'
                  : ''
              ]"
              @click="onChangeStu('after')"
            >
              下一个学生
            </div>
          </div>
        </template>
        <el-empty v-else description="暂无学生" />
      </div>
      <div class="content-right flex-column">
        <div class="index-line flex-between">
          <span class="title" v-if="curTaskInfo"
            >题目：{{ curTaskInfo.index }}</span
          >
          <div class="flex">
            <div
              class="btn hover"
              v-if="curTaskInfo"
              @click="isShowParser = !isShowParser"
            >
              {{ isShowParser ? '关闭答案解析' : '查看答案解析' }}
            </div>
            <div class="btn hover" v-if="curTaskInfo" @click="isShow = !isShow">
              {{ isShow ? '关闭原题' : '查看原题' }}
            </div>
          </div>
        </div>
        <template v-if="curTaskInfo">
          <div class="answer-content">
            <div class="stem-box" v-show="isShow">
              <Topic :topicData="curTaskInfo.question_detail" />
            </div>
            <div class="stem-box" v-show="isShowParser">
              <Topic
                :topicData="curTaskInfo.question_detail"
                v-model:showTopicParser="isShowParser"
                :onlyParser="true"
              />
            </div>

            <div class="answer-box">
              <div class="title">学生答题</div>
              <div
                v-if="!curTaskInfo.sub_question_info"
                v-html="
                  getNormalizeData(
                    JSON.parse(curTaskInfo.response || JSON.stringify([])),
                    getParseData(curTaskInfo.question_detail)
                  )
                "
              ></div>
              <template
                v-if="
                  curTaskInfo.sub_question_info &&
                  curTaskInfo.sub_question_info.length
                "
              >
                <div
                  v-for="(
                    subResponse, subIndex
                  ) in curTaskInfo.sub_question_info"
                  :key="subIndex"
                  v-html="
                    getNormalizeData(
                      JSON.parse(subResponse.response || JSON.stringify([])),
                      getParseData(
                        curTaskInfo.question_detail.subproblem[subIndex]
                      )
                    )
                  "
                ></div>
              </template>
              <PictureList
                v-if="!isAddingAnnotation && imgUrl.length"
                :img-url="imgUrl"
                v-model:imgIndex="pictureIndex"
                :student-name="studentList[curStudentIndex]?.student_name"
                :question-index="curTaskInfo.index"
              />
              <div class="correct-detail-annotation-box">
                <AnnotationBox
                  v-if="isAddingAnnotation && maskType === 'pic'"
                  :img-url="imgUrl[pictureIndex]"
                />
              </div>
            </div>
          </div>
          <div class="text-box" v-if="!isAddingAnnotation && annotationText">
            文本批注：{{ annotationText }}
          </div>
          <div class="tool-box flex-around">
            <AnnotationControl
              v-if="isAddingAnnotation && maskType === 'pic'"
            />
            <AnnotationText
              v-else-if="isAddingAnnotation && maskType === 'text'"
              @cancel="onToggleMark"
              @update="onUpdateText"
              :value="annotationText"
            />
            <template v-else>
              <img
                class="btn-img hover"
                :class="[taskIndex === 0 && 'btn-img-disable']"
                src="@/assets/images/assignment/btn-left.png"
                @click="onChangeTask('pre')"
              />
              <div class="btn-list flex">
                <div
                  class="list-btn hover flex-center"
                  v-for="(btn, index) in btnList"
                  :key="index"
                  :style="{ backgroundColor: btn.color }"
                  @click="postTeacherFeedBackInfo(btn.type)"
                >
                  <img
                    :src="btn.img"
                    class="btn-img"
                    :class="[
                      !taskList.length || index === taskList.length - 1
                        ? 'btn-img-disable'
                        : ''
                    ]"
                  />
                  {{ btn.text }}
                </div>
              </div>
              <div class="flex">
                <el-button
                  type="primary"
                  text
                  class="annotation-btn"
                  @click="onToggleMark"
                >
                  <AnnotationBtn class="img" />
                  批注
                </el-button>
                <img
                  class="btn-img hover"
                  :class="[
                    taskIndex === taskList.length - 1 && 'btn-img-disable'
                  ]"
                  @click="onChangeTask('after')"
                  src="@/assets/images/assignment/btn-right.png"
                />
              </div>
            </template>
          </div>
        </template>
        <el-empty class="empty-box" v-else description="暂无批改题目" />
      </div>
    </main>
  </div>
</template>

<script setup>
import { ref, computed, watch } from 'vue'
import { useRoute } from 'vue-router'
import router from '@/router'
import {
  getPracticeDetail,
  getQuestionByTaskId,
  postTeacherFeedBack,
  postCollect
} from '@/apis/assignment'
import { useAuthStore } from '@/stores'
import { getNormalizeData, getParseData } from '@/utils/answer'
import { annotateMitt } from '@/utils/tools/bus'
import Topic from '@/components/rb-topic/Topic.vue'
import Breadcrumb from '@/components/Breadcrumb.vue'
import PictureList from '@/components/picture-preview/PictureList.vue'
import right from '@/assets/images/assignment/right.png'
import half from '@/assets/images/assignment/half.png'
import wrong from '@/assets/images/assignment/wrong.png'
import { ElMessage } from 'element-plus'
import { useSingleQtsCorrectStore } from '@/stores/single-correct'
import { cloneDeep } from 'lodash'
import AnnotationControl from '@/components/annotation/AnnotationControl.vue'
import AnnotationBtn from '@/assets/images/assignment/annotation.svg'
import AnnotationBox from '@/components/annotation/AnnotationBox.vue'
import AnnotationText from '@/components/annotation/AnnotationText.vue'

const singleQtsCorrectStore = useSingleQtsCorrectStore()

const isShow = ref(true)
const isShowParser = ref(false)
const btnList = ref([
  {
    color: '#0CC58D',
    text: '正确',
    img: right,
    type: 2
  },
  {
    color: '#FFB84F',
    text: '半对',
    img: half,
    type: 1
  },
  {
    color: '#FB7E4C',
    text: '错误',
    img: wrong,
    type: 0
  }
])
const route = useRoute()

const authStore = useAuthStore()
const taskInfo = ref({
  taskId: '',
  name: '',
  classList: [],
  maskType: null // 任务的批改方式
})
const selectClass = ref()
const taskList = ref([])
const taskIndex = ref(null)
const curTaskInfo = computed(() => {
  return taskList.value[taskIndex.value]
})
watch(
  () => curTaskInfo.value,
  () => {
    if (!curTaskInfo.value) return
    let urls = curTaskInfo.value?.response_url
      ? JSON.parse(curTaskInfo.value.response_url)
      : []
    let { sub_question_info } = curTaskInfo.value
    if (sub_question_info) {
      sub_question_info.forEach(element => {
        let url = JSON.parse(element.response_url)
        urls.push(...url)
      })
    }
    imgUrl.value = urls
    resetAnno()
  }
)

const studentList = ref([])
const curStudentIndex = ref(null)

// ==== start 批注相关
const pictureIndex = ref(0)
const isAddingAnnotation = ref(false) // 是否开启批注
const annotationText = ref('')
const imgUrl = ref([])
const resetAnno = () => {
  isAddingAnnotation.value = false
  annotationText.value = ''
  pictureIndex.value = 0
}
const onToggleMark = () => {
  isAddingAnnotation.value = !isAddingAnnotation.value
  if (!isAddingAnnotation.value) resetAnno()
}
const onUpdateText = value => {
  annotationText.value = value
  isAddingAnnotation.value = false
}

const annotateMittListener = () => {
  annotateMitt.on('annotationControl', param => {
    let { model } = param
    switch (model) {
      case 'cancel':
        isAddingAnnotation.value = false
        break
      case 'save-img-url':
        isAddingAnnotation.value = false
        imgUrl.value[pictureIndex.value] = param.url
        break
    }
  })
}
const maskType = computed(() => {
  return imgUrl.value.length ? 'pic' : 'text'
})
// ==== end 批注相关

const onChangeStu = type => {
  if (!studentList.value.length) return
  if (type === 'pre') {
    curStudentIndex.value =
      curStudentIndex.value === 0 ? 0 : curStudentIndex.value - 1
  } else if (type === 'after') {
    curStudentIndex.value =
      curStudentIndex.value === studentList.value.length - 1
        ? curStudentIndex.value
        : curStudentIndex.value + 1
  } else {
    curStudentIndex.value = type
  }
}
const onChangeTask = type => {
  if (!taskList.value.length) return
  if (type === 'pre') {
    taskIndex.value = taskIndex.value === 0 ? 0 : taskIndex.value - 1
  } else if (type === 'after') {
    taskIndex.value =
      taskIndex.value === taskList.value.length - 1
        ? taskIndex.value
        : taskIndex.value + 1
  }
}

let message = null
/**
 * 老师批改
 */
const postTeacherFeedBackInfo = async correctType => {
  let param = {
    question_id: curTaskInfo.value.question_detail.id,
    teacher_id: Number(authStore.userInfo.userId),
    task_id: Number(taskInfo.value.taskId),
    student_id: Number(studentList.value[curStudentIndex.value].student_id),
    teacher_correct: -1
  }
  if (curTaskInfo.value.sub_question_info?.length) {
    let subParam = curTaskInfo.value.sub_question_info[0]
    param.children_question_info = [
      {
        question_id: subParam.children_question_id,
        question_type: subParam.question_type,
        teacher_evaluate: annotationText.value,
        teacher_evaluate_url: imgUrl.value,
        teacher_correct: correctType
      }
    ]
  } else {
    param = {
      ...param,
      teacher_correct: correctType,
      teacher_evaluate: annotationText.value,
      teacher_evaluate_url: imgUrl.value
    }
  }
  const res = await postTeacherFeedBack(param)
  if (res.code === 1) {
    resetAnno()
    // 数据埋点
    postCollect({
      action_type: 4,
      task_id: taskInfo.value.taskId
    })

    // 切换题目索引
    taskList.value.splice(taskIndex.value, 1)
    if (taskList.value.length === 0) {
      taskIndex.value = null
    } else if (taskIndex.value === taskList.value.length) {
      taskIndex.value = 0
    }
    // 是否需要减一
    if (
      taskList.value.findIndex(
        item => item.question_id === param.question_id
      ) === -1
    ) {
      studentList.value[curStudentIndex.value].un_grade_count--
    }
    if (message) {
      message.close()
    }
    message = ElMessage.success('批改成功')
  }
}

/**
 * 查看任务下的题目
 */
const getQuestionListInfo = async () => {
  if (curStudentIndex.value === null) return
  let param = {
    task_id: taskInfo.value.taskId,
    student_id: studentList.value[curStudentIndex.value].student_id,
    class_id: selectClass.value.classId,
    class_type: selectClass.value.class_type
  }
  const res = await getQuestionByTaskId(param)
  let list = res.data.question_info || []
  list = list.map((question, index) => {
    let subQuestion = []
    if (question.sub_question_info?.length) {
      let { sub_question_info } = question
      sub_question_info.map((sub, subIndex) => {
        let paramQuestion = cloneDeep(question)
        paramQuestion.question_detail.subproblem =
          paramQuestion.question_detail.subproblem.filter(
            item => item.id == sub.children_question_id
          )
        paramQuestion.sub_question_info =
          paramQuestion.sub_question_info.filter(
            item => item.children_question_id == sub.children_question_id
          )
        paramQuestion.index = index + 1 + '-' + (subIndex + 1)
        subQuestion.push(paramQuestion)
      })
      return subQuestion
    } else {
      question.index = index + 1
      return question
    }
  })
  list = list.flat()
  taskList.value = list.filter(question => {
    if (question.sub_question_info?.length) {
      let subQuestion = question.sub_question_info[0]
      return subQuestion.submit === 1 && subQuestion.teacher_correct === -1
    }
    return question.submit === 1 && question.teacher_correct === -1
  })
  if (taskList.value.length) {
    taskIndex.value = 0
  }
}

/**
 * 获取当前任务批改学生
 */
const getPracticeDetailInfo = async () => {
  const res = await getPracticeDetail({
    task_id: taskInfo.value.taskId,
    class_id: selectClass.value.classId,
    class_type: selectClass.value.class_type
  })
  const { submit_list, task_statistics } = res.data
  studentList.value = submit_list.list.filter(
    student => student.un_grade_count > 0
  )
  curStudentIndex.value = null
  taskList.value = []
  taskInfo.value.maskType = task_statistics.correct_type
  if (studentList.value.length) {
    curStudentIndex.value = 0
  }
}

/**
 * 去按题批改
 */
const toSingleCorrect = () => {
  singleQtsCorrectStore.taskId = taskInfo.value.taskId
  singleQtsCorrectStore.classId = selectClass.value.classId
  singleQtsCorrectStore.classType = selectClass.value.class_type
  router.push({
    name: 'singleCorrect',
    query: {
      taskId: taskInfo.value.taskId,
      classId: selectClass.value.classId,
      classType: selectClass.value.class_type,
      correctType: taskInfo.value.maskType
    }
  })
}

watch(
  () => curStudentIndex.value,
  () => {
    if (curStudentIndex.value >= 0) {
      getQuestionListInfo()
    }
  },
  {
    deep: true
  }
)

watch(
  () => selectClass.value,
  () => {
    getPracticeDetailInfo()
  },
  {
    deep: true
  }
)

const initData = () => {
  annotateMittListener()

  taskInfo.value = {
    taskId: route.query?.taskId,
    name: route.query?.name,
    classList: JSON.parse(route.query?.classList)
  }
  if (route.query?.activeClassId) {
    selectClass.value = taskInfo.value.classList.find(
      item => item.classId == route.query?.activeClassId
    )
    return
  }

  selectClass.value = taskInfo.value.classList[0]
}

initData()
</script>

<style lang="less" scoped>
.correct-detail-container {
  .jump-btn {
    cursor: pointer;
    width: 120px;
    height: 40px;
    line-height: 40px;
    background-color: #3d54d9;
    color: #fff;
    border-radius: 6px;
    font-size: @size-big;
    text-align: center;
  }
  .content {
    margin-top: 20px;
    gap: 20px;
    align-items: self-start;
    height: calc(100vh - 140px);

    .content-left {
      height: 100%;
      background-color: #fff;
      padding: 20px;
      border-radius: 10px;
      width: 420px;

      .left-title {
        width: 240px;
        font-size: 20px;
        font-weight: bold;
      }

      .title {
        font-size: 18px;
        margin: 10px 0;
      }

      .student-list {
        height: calc(100% - 140px);
        overflow: auto;
        gap: 20px;

        .student-item {
          padding: 14px;
          border-radius: 8px;
          background-color: #fafafa;

          .count {
            color: #5466e7;
          }
        }

        .student-item-active {
          background-color: #e9eeff;
          color: #5466e7;
        }
      }

      .btn-list {
        gap: 20px;
        margin-top: 12px;

        .btn-item {
          flex: 1;
          color: #5466e7;
          background-color: rgb(247 249 255 / 1);
          height: 50px;
          border-radius: 8px;
        }

        .disabled:hover {
          cursor: not-allowed;
        }
      }
    }

    .content-right {
      height: 100%;
      background-color: #fff;
      padding: 20px;
      border-radius: 10px;
      flex: 1;
      overflow-x: hidden;
      position: relative;

      .index-line {
        margin-bottom: 20px;

        .title {
          font-weight: bold;
        }

        .btn {
          line-height: 2;
          padding: 0px 10px;
          text-align: center;
          color: #5466e7;
          background-color: rgb(247 249 255 / 1);
          border-radius: 15px;
          margin-right: 20px;

          &:hover {
            color: #5466e7;
            background-color: #e0e4ff;
          }
        }
      }
      .answer-content {
        height: calc(100% - 90px);
        overflow-y: auto;
        overflow-x: hidden;
        .stem-box {
          margin-bottom: 20px;

          :deep(.topic-cpn) {
            min-height: unset;
            .more-box {
              border-top: unset;
              margin-top: unset;
              padding-top: unset;
            }
          }
        }

        .answer-box {
          flex: 1;
          min-height: 500px;
          overflow-y: auto;
          padding: 20px;
          margin-bottom: 20px;
          border-radius: 14px;
          background-color: #f7f9ff;

          .title {
            font-weight: bold;
            color: #5466e7;
            margin-bottom: 20px;
          }
        }
      }
      .text-box {
        margin: 0 20px;
        padding: 20px;
        border-radius: 20px;
        background-color: #fafafa;
      }
      .tool-box {
        margin-top: 10px;
        .btn-img {
          width: 50px;
        }

        .btn-img-disable:hover {
          cursor: not-allowed;
        }

        .btn-list {
          gap: 16px;

          .list-btn {
            width: 170px;
            height: 50px;
            line-height: 50px;
            text-align: center;
            border-radius: 8px;
            color: #fff;

            .btn-img {
              width: 20px;
              margin-right: 10px;
            }
          }
        }
        .annotation-btn {
          gap: 20px;
          margin-right: 20px;
          .img {
            margin-top: -2px;
            margin-right: 4px;
          }
        }
      }
      .correct-detail-annotation-box {
        width: 70%;
        margin: 0 auto !important;
      }
    }

    .empty-box {
      position: relative;
      top: 50%;
      transform: translateY(-50%);
    }
  }
}
</style>
